package com.edu.compile.compiler;

import com.edu.compile.AbstractCompileResult;
import com.edu.compile.AbstractCompilerParser;
import com.edu.compile.config.IfElseConfig;
import com.edu.compile.constant.ComparatorEnum;
import com.edu.compile.constant.SourceEnum;
import com.edu.compile.metadata.ConditionMetadata;
import com.edu.compile.metadata.SourceMetadata;
import com.edu.compile.template.ftl.block.IfElse;
import com.edu.compile.template.model.IfTrue;
import com.edu.compile.template.model.IfTrueConfig;
import com.edu.model.dto.NodeMetadata;
import org.springframework.stereotype.Component;

import java.util.ArrayList;
import java.util.List;

@Component("if_else_compiler")
public class IfElseCompiler extends AbstractCompilerParser<IfElseConfig, IfElse> {

    @Override
    public void compile(AbstractCompileResult abstractCompileResult, NodeMetadata nodeMetadata, IfElseConfig ifElseConfig, IfElse ifElse) {

        String logicRelation = ifElseConfig.getLogicRelation();
        List<ConditionMetadata> conditions = ifElseConfig.getConditions();

        IfTrue ifTrue = new IfTrue();
        ifTrue.setLogicRelation(logicRelation);
        List<IfTrueConfig> conditionList = new ArrayList<>();
        ifTrue.setConditionList(conditionList);

        ifElse.setIfTrue(ifTrue);
        conditions.forEach(condition -> {
            SourceMetadata left = condition.getLeft();
            SourceMetadata right = condition.getRight();
            String comparator = condition.getComparator();

            IfTrueConfig ifTrueConfig = new IfTrueConfig();
            Object leftValue = getValue(left, ifElse);
            ifTrueConfig.setLeft(leftValue);

            if (!ComparatorEnum.exists(comparator)) {
                throw new IllegalArgumentException("comparator not supported");
            }
            ifTrueConfig.setComparator(comparator);
            if (!ComparatorEnum.non.testOr(comparator, ComparatorEnum.neq)) {
                if (right == null) {
                    throw new IllegalArgumentException("param must not be empty");
                }
                Object rightValue = getValue(right, ifElse);
                ifTrueConfig.setRight(rightValue);
            }
            conditionList.add(ifTrueConfig);
        });
    }

    private Object getValue(SourceMetadata config, IfElse ifElse) {
        if (SourceEnum.FIXED.test(config.getSource())) {
//            Object wrapper = ParamTypeEnum.convert(config.getType(), config.getValue());
//            return wrapper;
            return config.getValue();
        } else {
            ifElse.addUndefinedCheck(config.getPort());
            ifElse.addUndefinedCheck(config.getValue().toString());
            return config.getValue();
        }
    }
}
